#include "cube.h"

CCube::CCube(void)
{
	cube = NULL;
}

CCube::~CCube(void)
{
}

void CCube::parseMessage(Message& msg, vector<Message>& retMsg)
{
	switch(msg.MsgCode)
	{
	case MSG_INIT:
		{
//test test test
		}
	case MSG_UPDATE:
		{
		}
		break;

	case MSG_DRAW:
		break;
	}
}


void CCube::Rotate(int direction)
{
	CArray3D *rotatedCube;

	int xsize = cube->getXsize();
	int ysize = cube->getYsize();
	int zsize = cube->getZsize();

	switch(direction)
	{
	case ROT_LEFT:
		rotatedCube = new CArray3D(zsize, ysize, xsize);
		for(int i=0; i < xsize; i++)
			for(int j=0; j < ysize; j++)
				for(int k=0; k < zsize; k++)
					(*rotatedCube)(k, j, xsize-i-1) = (*cube)(i,j,k);
		break;

	case ROT_RIGHT:
		rotatedCube = new CArray3D(zsize, ysize, xsize);
		for(int i=0; i < xsize; i++)
			for(int j=0; j < ysize; j++)
				for(int k=0; k < zsize; k++)
					(*rotatedCube)(zsize-k-1, j, i) = (*cube)(i,j,k);
		break;

	case ROT_CLKWISE:
		rotatedCube = new CArray3D(ysize, xsize, zsize);
		for(int i=0; i < xsize; i++)
			for(int j=0; j < ysize; j++)
				for(int k=0; k < zsize; k++)
					(*rotatedCube)(j, xsize-i-1, k) = (*cube)(i,j,k);
		break;

	case ROT_CCLKWISE:
		rotatedCube = new CArray3D(ysize, xsize, zsize);
		for(int i=0; i < xsize; i++)
			for(int j=0; j < ysize; j++)
				for(int k=0; k < zsize; k++)
					(*rotatedCube)(ysize-j-1, i, k) = (*cube)(i,j,k);
		break;
	}

	delete cube;
	cube = rotatedCube;
}

CCoords* CCube::getNewCoords(const CCoords* old, int rotDirection)
{
	CCoords* newCoords;

	switch(rotDirection)
	{
	case ROT_LEFT:
		newCoords = new CCoords(old->getZ(), 
								old->getY(), 
								cube->getXsize() - old->getX() - 1
								);
		break;

	case ROT_RIGHT:
		newCoords = new CCoords(cube->getZsize() - old->getZ() - 1,
								old->getY(), 
								old->getX()
								);
		break;

	case ROT_CLKWISE:
		newCoords = new CCoords(old->getY(), 
								cube->getXsize() - old->getX() - 1,
								old->getZ()
								);
		break;

	case ROT_CCLKWISE:
		newCoords = new CCoords(cube->getYsize() - old->getY() - 1,
								old->getX(),
								old->getZ()
								);
		break;
	}
	return newCoords;
	// TODO: 
	// move new's to begin
	// make default branch
}

CArray2D* CCube::getSurrCells(const CCoords* pos)
{
	CArray2D* surrCells = new CArray2D(3,3);
	for(int i=0; i<3; i++)
		for(int j=0; j<3; j++)
			(*surrCells)(i,j)=(*cube)(pos->getX()+i-1,pos->getY()+j-1,pos->getZ());
	return surrCells;
}

CArray2D* CCube::getCrossSection(const CCoords* pos)
{
	CArray2D* crSec = new CArray2D(cube->getXsize(),cube->getYsize());
	for(int i=0; i<cube->getXsize(); i++)
		for(int j=0; j<cube->getYsize(); j++)
			(*crSec)(i,j)=(*cube)(i,j,pos->getZ());
	return crSec;
}